#pragma once

class Block;

class Grid
{
public:
	enum T_DIRECTION
	{
		LEFT = (1 << 1),
		RIGHT = (1 << 2),
		DOWN = (1 << 3),
		UP = (1 << 4)
	};

	Grid();
	~Grid();
	
	void Update( float a_DT );

	void Render( float a_DT );

	void MoveCurrentStructure( T_DIRECTION a_Direction );
	void RotateCurrentStructure( T_DIRECTION a_Direction );
	
	int GetNextBlockIndex();
	Block::T_TYPE GetNextBlockType();
	int GetNextBlockRotation();
	CIw2DImage* GetBlockTypeImage( Block::T_TYPE a_Type );

	bool BlockWasMoved();

	bool m_BlockPatterns[8][4][4][4];
	CIw2DImage** m_BlockTypeImages;
private:
	void ClearLine( int a_Line );
	void CheckLines();

	/*
		Spawns the desired block with the desired rotation at the top of the screen. if a_CheckValid is true, also checks to see if
		the block can be spawned at that location and signals the game if the block can't be spawned. Because in that case, the game
		is over.
	*/
	void SpawnBlocks( int a_StructureIndex, int a_StructureRotation, bool a_CheckValid = true );
	void SwapBlocks( int a_Index1, int a_Index2 );

	Block** m_Blocks;

	int m_NextBlockIndex;
	Block::T_TYPE m_NextBlockType;
	int m_NextBlockRotation;
	// Current block data.
	int m_CurrentGroupID;	// Contains the group ID of the group that was last spawned.
	Block* m_CurBlocks[4];
	int m_CurBlockPattern;
	int m_CurBlockRotation;
	CIwSVec2 m_CurBlockPos;

	// Block management.
	bool m_BlockWasMoved;
	float m_BlockMoveTimer;
	float m_BlockSize;

	CIwSVec2 m_GridTopLeft;
	CIwSVec2 m_GridBGTopLeft;
	CIwSVec2 m_GridBGSize;

	CIw2DImage* m_DefaultBlockImage;
	CIw2DImage* m_Background;
};